﻿#pragma once

#include <QtWidgets/QWidget>
#include "ui_WriteWindow.h"
#include "Context/VideoProgram.h"
#include "Device/InputDevice.h"
#include "Device/OutputDevice.h"
#include "Coder/H264Encoder.h"
#include "Coder/Mp4Encoder.h"
#include "Coder/AACEncoder.h"

class WriteWindow : public QWidget
{
    Q_OBJECT

public:
    WriteWindow(QWidget *parent = Q_NULLPTR);

protected:
    void closeEvent(QCloseEvent* e);

private slots:
    // 开始预览
    void on_start_clicked();

    // 停止预览
    void on_stop_clicked();

    // 数据在主线程回调给渲染器(防止窗口动态变化崩溃)
    void onBuffer();

    // 摄像头选择
    void on_videoDevice_currentIndexChanged(int index);

    // 分辨率选择
    void on_videoInfo_currentIndexChanged(int index);

    // 麦克风选择
    void on_audioDevice_currentIndexChanged(int index);

signals:
    void sendBuffer();

private:
    Ui::WriteWindowClass ui;

    // 视频控件
    VideoProgram* _videoProgram;
    InputDevice* _inputDevice;

    // 声音预览
    OutputDevice _outputDevice;
    CircleBuffer _pcmBuffer;

    // 摄像头
    DShow::VideoDevice _selectVideoDevice;
    DShow::VideoInfo _selectVideoInfo;
    std::vector<DShow::VideoDevice> _videoDevices;

    // 麦克风
    DShow::AudioDevice _selectAudioDevice;
    std::vector<DShow::AudioDevice> _audioDevices;

    // h264编码器
    H264Encoder _h264Ecoder;

    // mp4编码器
    int startTime = 0;
    Mp4Encoder _mp4Coder;

    // acc编码器
    AACEncoder _accEncoder;

    // 摄像头数据回调
    void videoBuffer();

    // 麦克风数据回调
    void audioBuffer(const DShow::AudioConfig& config, unsigned char* data,
        size_t size, long long startTime, long long stopTime);

    // 声音播放器回调
    void playAudio(void* buffer, unsigned long size);

    // 枚举摄像头
    void enumVideoDevices();

    // 枚举麦克风
    void enumAudioDevices();
};
